﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Mvc;
using Unijovem.Domain;
using Unijovem.UI.Helpers;
using Unijovem.UI.Models;

namespace Unijovem.UI.Controllers
{
    public class PessoaController : ControllerBase<PessoaModel, Pessoa>
    {
        public override ActionResult Manter(PessoaModel model)
        {
            model.DataCadastro = model.Usuario.DataInclusao = model.Usuario.DataUltimoAcesso = DateTime.Now;
            model.Usuario.Senha = Domain.Helpers.Util.Criptografar(model.Usuario.Senha);

            base.Manter(model);

            if (Model == null) return View(model);

            EnviarEmailConfirmacao(Model);
            PreencherViewBags();
            return View(Model);
        }

        public ActionResult ReenviarSenha(int id = 0)
        {
            if (id == 0)
            {
                var model = new PessoaModel().CriarViewModel(new Pessoa().SelecionarPessoaLoginInativo());
                foreach (var pessoaModel in model)
                    EnviarEmailConfirmacao(pessoaModel);
            }
            else
            {
                var model = new PessoaModel().CriarViewModel(new Pessoa().SelectById<Pessoa>(id));
                EnviarEmailConfirmacao(model);
            }

            return View();
        }

        public void PreencherViewBags(string sexo = null)
        {
            var sexoLista = new Dictionary<string, string> { { "F", "Feminino" }, { "M", "Masculino" } };
            ViewBag.Sexo = sexoLista.ToSelectList(g => g.Value, g => g.Key, "Sexo", sexo ?? "F");
        }

        public ActionResult ManterAdministrador()
        {
            return View();
        }

        public ActionResult VerificarEmailJaCadastrado(string email)
        {
            return Json(new { success = !new Pessoa().VerificarEmailJaCadastrado(email) });
        }

        [HttpPost]
        public ActionResult ManterAdministrador(PessoaModel model)
        {
            model.Usuario = new UsuarioModel { Senha = Guid.NewGuid().ToString().Trim().ToLower().Substring(0, 6), Ativo = true };
            return Manter(model);
        }

        public ActionResult EmailCadastro(int id)
        {
            var dominio = new Pessoa().SelectById<Pessoa>(id);
            var pessoa = new PessoaModel().CriarViewModel(dominio);

            return PartialView(pessoa);
        }

        public ActionResult EmailEsqueciSenha(int id)
        {
            var dominio = new Pessoa().SelectById<Pessoa>(id);
            var pessoa = new PessoaModel().CriarViewModel(dominio);

            return PartialView(pessoa);
        }

        private void EnviarEmailConfirmacao(PessoaModel pessoa)
        {
            var email = new MailHelper.Email
            {
                From = ContaEmailHelper.ObterConta(ContaEmailHelper.Conta.NaoResponder),
                Subject = "Bem-vindo à UnijovemIBVG.com.br",
                TemplatePath = string.Concat(Url.Action("EmailCadastro", "Pessoa", 0, "http"), "/", pessoa.Id),
                To = pessoa
            };

            MailHelper.SendTemplatedEmail(email);
        }

        public ActionResult MeuPerfil()
        {
            return RedirectToAction("Perfil");
        }

        public ActionResult AtualizarUltimaVezOnline()
        {
            if (WebSession<Pessoa>(SessionName.PessoaLogada) == null) return Json(new { success = false });

            var pessoa = WebSession<Pessoa>(SessionName.PessoaLogada);
            pessoa.Usuario.UltimaVezOnline = DateTime.Now;
            pessoa.Usuario.StatusChat = ((int) UsuarioModel.StatusEnum.Online).ToString();
            pessoa.Usuario.Save(pessoa.Usuario);
            WebSession(SessionName.PessoaLogada, pessoa);

            return Json(new { success = true });
        }

        public ActionResult Perfil(int? id = null)
        {
            if (id == null && PessoaLogada == null)
                return RedirectToAction("Index", "Home");

            var dominio = id != null
                              ? new Pessoa().SelectById<Pessoa>(id.Value)
                              : PessoaLogada;

            var pessoa = new PessoaModel().CriarViewModel(dominio);
            pessoa.AtividadesRecentes = PreencherAtividadesRecentes(dominio);
            pessoa.UsuarioEstaLogado = id == null;
            return View(pessoa);
        }

        public ActionResult PerfilCampos(bool logado, int? idPessoa = null)
        {
            if (idPessoa == null && PessoaLogada == null)
                return RedirectToAction("Index", "Home");

            var perfis = new PerfilModel().CriarViewModel(idPessoa != null
                                                              ? new Pessoa().SelectById<Pessoa>(idPessoa.Value).Perfils
                                                              : PessoaLogada.Perfils).ToList();

            var campos = new CampoPerfilModel().CriarViewModel(new CampoPerfil().SelectAllActive<CampoPerfil>());

            if (UsuarioLogado)
                foreach (var campoPerfilModel in campos)
                    campoPerfilModel.UsuarioLogado = logado;

            if (!perfis.Any()) return PartialView(campos);

            //var valores = new ValorCampoPerfilModel().CriarViewModel(new ValorCampoPerfil().SelectAllActive<ValorCampoPerfil>());

            foreach (var campoPerfil in campos)
            {
                //campoPerfil.ValorCampoPerfis = valores.Where(valor => valor.IdCampoPerfil == campoPerfil.Id).ToList();
                var perfil = perfis.FirstOrDefault(p => p.IdCampoPerfil == campoPerfil.Id);

                if (perfil == null) continue;

                campoPerfil.Perfil = perfil;
                perfis.Remove(perfil);
            }

            return PartialView(campos);
        }

        [HttpPost]
        public ActionResult PerfilCampos(FormCollection collection)
        {
            var idPessoa = PessoaLogada.Id;
            var perfis = new Pessoa().SelectById<Pessoa>(idPessoa).Perfils;

            foreach (var key in collection.AllKeys)
            {
                var idCampoPerfil = int.Parse(key.ToLower().Replace("input", string.Empty));
                var perfil = perfis.FirstOrDefault(p => p.IdCampoPerfil == idCampoPerfil);
                var valor = collection.GetValue(key).AttemptedValue.Replace("true,false", "true");

                if (perfil == null)
                {
                    if (string.IsNullOrEmpty(valor)) continue;

                    new Perfil { IdCampoPerfil = idCampoPerfil, IdPessoa = idPessoa, Valor = valor }.Save();
                }
                else
                {
                    if (valor == perfil.Valor) continue;

                    perfil.Valor = valor;
                    perfil.Save(perfil);
                }
            }

            return PerfilCampos(true);
        }

        private List<AtividadeRecenteModel> PreencherAtividadesRecentes(Pessoa pessoa)
        {
            var atividadesRecentes = new List<AtividadeRecenteModel>();

            atividadesRecentes.AddRange(PreencherComentariosDevocionalRecente(pessoa));
            atividadesRecentes.AddRange(PreencherComentariosLeituraRecente(pessoa));
            atividadesRecentes.AddRange(PreencherComentariosMusicaRecente(pessoa));
            atividadesRecentes.AddRange(SelecionarForunsRecentes(pessoa));
            atividadesRecentes.AddRange(SelecionarEnquetesRecentes(pessoa));
            atividadesRecentes.AddRange(SelecionarLeiturasRecentes(pessoa));

            return atividadesRecentes.Count == 0 ? null : atividadesRecentes.OrderByDescending(a => a.Data).ToList();
        }

        private IEnumerable<AtividadeRecenteModel> PreencherComentariosMusicaRecente(Pessoa pessoa)
        {
            return pessoa.Comentarios.Where(c => c.Data >= DateTime.Today.AddDays(-30) && c.MusicaComentarios != null && c.MusicaComentarios.Count > 0).Select(
                    a => new AtividadeRecenteModel
                    {
                        Url = Url.Action("Detalhes", "Musica", new { id = a.MusicaComentarios.First().IdMusica }),
                        Data = a.Data,
                        Descricao = string.Concat("Comentou na música '", a.MusicaComentarios.First().Musica.Titulo, "'")
                    });
        }

        private IEnumerable<AtividadeRecenteModel> PreencherComentariosLeituraRecente(Pessoa pessoa)
        {
            return pessoa.Comentarios.Where(c => c.Data >= DateTime.Today.AddDays(-30) && c.LeituraBiblicaComentarios != null && c.LeituraBiblicaComentarios.Count > 0).Select(
                a => new AtividadeRecenteModel
                         {
                             Url =
                                 Url.Action("Diaria", "LeituraBiblica",
                                            new
                                                {
                                                    dia = a.LeituraBiblicaComentarios.First().LeituraBiblica.Dia,
                                                    ordem = a.LeituraBiblicaComentarios.First().LeituraBiblica.Ordem - 1
                                                }),
                             Data = a.Data,
                             Descricao = string.Concat("Comentou na leitura diária do ",
                                                       a.LeituraBiblicaComentarios.First().LeituraBiblica.Dia,
                                                       "º dia. Versículo: ",
                                                       a.LeituraBiblicaComentarios.First().LeituraBiblica.Versiculo)
                         });
        }

        private IEnumerable<AtividadeRecenteModel> PreencherComentariosDevocionalRecente(Pessoa pessoa)
        {
            return pessoa.Comentarios.Where(c => c.Data >= DateTime.Today.AddDays(-30) && c.DevocionalComentarios != null && c.DevocionalComentarios.Count > 0).Select(
                    a => new AtividadeRecenteModel
                             {
                                 Url = Url.Action("DetalhesLeitura", "Devocional", new { id = a.DevocionalComentarios.First().IdDevocional }),
                                 Data = a.Data,
                                 Descricao = string.Concat("Comentou na devocional '", a.DevocionalComentarios.First().Devocional.Titulo, "'")
                             });
        }

        private IEnumerable<AtividadeRecenteModel> SelecionarLeiturasRecentes(Pessoa pessoa)
        {
            return pessoa.Usuario.LeituraBiblicaUsuarios.Where(c => c.Data >= DateTime.Today.AddDays(-30)).Select(
                    a => new AtividadeRecenteModel
                             {
                                 Url = Url.Action("Diaria", "LeituraBiblica", new { dia = a.LeituraBiblica.Dia, ordem = a.LeituraBiblica.Ordem - 1 }),
                                 Data = a.Data,
                                 Descricao = string.Concat("Fez a leitura diária do ", a.LeituraBiblica.Dia, "º dia. Versículo: ", a.LeituraBiblica.Versiculo)
                             });
        }

        private IEnumerable<AtividadeRecenteModel> SelecionarEnquetesRecentes(Pessoa pessoa)
        {
            return pessoa.EnqueteRespostas.Where(c => c.Data >= DateTime.Today.AddDays(-30)).Select(
                    a => new AtividadeRecenteModel
                             {
                                 Url = Url.Action("Visualizar", "Enquete", new { id = a.IdEnquete }),
                                 Data = a.Data,
                                 Descricao = string.Concat("Respondeu à enquete '", a.Enquete.Pergunta, "'")
                             });
        }

        private IEnumerable<AtividadeRecenteModel> SelecionarForunsRecentes(Pessoa pessoa)
        {
            return pessoa.Comentarios.Where(
                c => c.Data >= DateTime.Today.AddDays(-30) && c.ForumComentarios != null && c.ForumComentarios.Count > 0)
                .Select(a => new AtividadeRecenteModel
                             {
                                 Url = Url.Action("Participar", "Forum", new { id = a.ForumComentarios.First().IdForum }),
                                 Data = a.Data,
                                 Descricao = string.Concat("Participou do forum '", a.ForumComentarios.First().Forum.Assunto, "'")
                             });
        }
    }
}
